home *** CD-ROM | disk | FTP | other *** search
/ Linux Cubed Series 7: Sunsite / Linux Cubed Series 7 - Sunsite Vol 1.iso / system / network / manageme / tcpdump-.001 / tcpdump-~ / tcpdump-3.0.2-linux / tcpdump-3.0.2 / print-isoclns.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-06-15  |  6.4 KB  |  316 lines

  1. /*
  2.  * Copyright (c) 1992, 1993, 1994
  3.  *    The Regents of the University of California.  All rights reserved.
  4.  *
  5.  * Redistribution and use in source and binary forms, with or without
  6.  * modification, are permitted provided that: (1) source code distributions
  7.  * retain the above copyright notice and this paragraph in its entirety, (2)
  8.  * distributions including binary code include the above copyright notice and
  9.  * this paragraph in its entirety in the documentation or other materials
  10.  * provided with the distribution, and (3) all advertising materials mentioning
  11.  * features or use of this software display the following acknowledgement:
  12.  * ``This product includes software developed by the University of California,
  13.  * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
  14.  * the University nor the names of its contributors may be used to endorse
  15.  * or promote products derived from this software without specific prior
  16.  * written permission.
  17.  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  18.  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  19.  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  20.  */
  21.  
  22. /*
  23.  * Original code by Matt Thomas, Digital Equipment Corporation
  24.  */
  25.  
  26. #ifndef lint
  27. static char rcsid[] =
  28.     "@(#) $Header: print-isoclns.c,v 1.9 94/06/14 20:18:44 leres Exp $ (LBL)";
  29. #endif
  30.  
  31. #include <sys/types.h>
  32. #include <sys/time.h>
  33. #include <sys/socket.h>
  34.  
  35. #include <net/if.h>
  36.  
  37. #include <netinet/in.h>
  38. #include <netinet/if_ether.h>
  39.  
  40. #include <stdio.h>
  41.  
  42. #include "interface.h"
  43. #include "addrtoname.h"
  44. #include "ethertype.h"
  45.  
  46. #define    CLNS    129
  47. #define    ESIS    130
  48. #define    ISIS    131
  49. #define    NULLNS    0
  50.  
  51. static int osi_cksum(const u_char *, int, const u_char *, u_char *, u_char *);
  52. static void esis_print(const u_char *, int);
  53.  
  54. void
  55. isoclns_print(const u_char *p, int length, int caplen,
  56.           const u_char *esrc, const u_char *edst)
  57. {
  58.     if (caplen < 1) {
  59.         printf("[|iso-clns] ");
  60.         if (!eflag)
  61.             printf("%s > %s",
  62.                    etheraddr_string(esrc),
  63.                    etheraddr_string(edst));
  64.         return;
  65.     }
  66.  
  67.     switch (*p) {
  68.  
  69.     case CLNS:
  70.         /* esis_print(&p, &length); */
  71.         printf("iso-clns");
  72.         if (!eflag)
  73.             (void)printf(" %s > %s",
  74.                      etheraddr_string(esrc),
  75.                      etheraddr_string(edst));
  76.         break;
  77.  
  78.     case ESIS:
  79.         printf("iso-esis");
  80.         if (!eflag)
  81.             (void)printf(" %s > %s",
  82.                      etheraddr_string(esrc),
  83.                      etheraddr_string(edst));
  84.         esis_print(p, length);
  85.         return;
  86.  
  87.     case ISIS:
  88.         printf("iso-isis");
  89.         if (!eflag)
  90.             (void)printf(" %s > %s",
  91.                      etheraddr_string(esrc),
  92.                      etheraddr_string(edst));
  93.         /* isis_print(&p, &length); */
  94.         (void)printf(" len=%d ", length);
  95.         if (caplen > 1)
  96.             default_print_unaligned(p, caplen);
  97.         break;
  98.  
  99.     case NULLNS:
  100.         printf("iso-nullns");
  101.         if (!eflag)
  102.             (void)printf(" %s > %s",
  103.                      etheraddr_string(esrc),
  104.                      etheraddr_string(edst));
  105.         break;
  106.  
  107.     default:
  108.         printf("iso-clns %02x", p[0]);
  109.         if (!eflag)
  110.             (void)printf(" %s > %s",
  111.                      etheraddr_string(esrc),
  112.                      etheraddr_string(edst));
  113.         (void)printf(" len=%d ", length);
  114.         if (caplen > 1)
  115.             default_print_unaligned(p, caplen);
  116.         break;
  117.     }
  118. }
  119.  
  120. #define    ESIS_REDIRECT    6
  121. #define    ESIS_ESH    2
  122. #define    ESIS_ISH    4
  123.  
  124. struct esis_hdr {
  125.     u_char version;
  126.     u_char reserved;
  127.     u_char type;
  128.     u_char tmo[2];
  129.     u_char cksum[2];
  130. };
  131.  
  132. static void
  133. esis_print(const u_char *p, int length)
  134. {
  135.     const u_char *ep;
  136.     int li = p[1];
  137.     const struct esis_hdr *eh = (const struct esis_hdr *) &p[2];
  138.     u_char cksum[2];
  139.     u_char off[2];
  140.  
  141.     if (length == 2) {
  142.         if (qflag)
  143.             printf(" bad pkt!");
  144.         else
  145.             printf(" no header at all!");
  146.         return;
  147.     }
  148.     ep = p + li;
  149.     if (li > length) {
  150.         if (qflag)
  151.             printf(" bad pkt!");
  152.         else
  153.             printf(" LI(%d) > PDU size (%d)!", li, length);
  154.         return;
  155.     }
  156.     if (li < sizeof(struct esis_hdr) + 2) {
  157.         if (qflag)
  158.             printf(" bad pkt!");
  159.         else {
  160.             printf(" too short for esis header %d:", li);
  161.             while (--length >= 0)
  162.                 printf("%02X", *p++);
  163.         }
  164.         return;
  165.     }
  166.     switch (eh->type & 0x1f) {
  167.  
  168.     case ESIS_REDIRECT:
  169.         printf(" redirect");
  170.         break;
  171.  
  172.     case ESIS_ESH:
  173.         printf(" esh");
  174.         break;
  175.  
  176.     case ESIS_ISH:
  177.         printf(" ish");
  178.         break;
  179.  
  180.     default:
  181.         printf(" type %d", eh->type & 0x1f);
  182.         break;
  183.     }
  184.     off[0] = eh->cksum[0];
  185.     off[1] = eh->cksum[1];
  186.     if (vflag && osi_cksum(p, li, eh->cksum, cksum, off)) {
  187.         printf(" bad cksum (got %02x%02x want %02x%02x)",
  188.                eh->cksum[1], eh->cksum[0], cksum[1], cksum[0]);
  189.         return;
  190.     }
  191.     if (eh->version != 1) {
  192.         printf(" unsupported version %d", eh->version);
  193.         return;
  194.     }
  195.     p += sizeof(*eh) + 2;
  196.     li -= sizeof(*eh) + 2;    /* protoid * li */
  197.  
  198.     switch (eh->type & 0x1f) {
  199.     case ESIS_REDIRECT: {
  200.         const u_char *dst, *snpa, *is;
  201.  
  202.         dst = p; p += *p + 1;
  203.         if (p > snapend)
  204.             return;
  205.         printf(" %s", isonsap_string(dst));
  206.         snpa = p; p += *p + 1;
  207.         is = p;   p += *p + 1;
  208.         if (p > snapend)
  209.             return;
  210.         if (p > ep) {
  211.             printf(" [bad li]");
  212.             return;
  213.         }
  214.         if (is[0] == 0)
  215.             printf(" > %s", etheraddr_string(&snpa[1]));
  216.         else
  217.             printf(" > %s", isonsap_string(is));
  218.         li = ep - p;
  219.         break;
  220.     }
  221. #if 0
  222.     case ESIS_ESH:
  223.         printf(" esh");
  224.         break;
  225. #endif
  226.     case ESIS_ISH: {
  227.         const u_char *is;
  228.  
  229.         is = p; p += *p + 1;
  230.         if (p > ep) {
  231.             printf(" [bad li]");
  232.             return;
  233.         }
  234.         if (p > snapend)
  235.             return;
  236.         printf(" %s", isonsap_string(is));
  237.         li = ep - p;
  238.         break;
  239.     }
  240.  
  241.     default:
  242.         (void)printf(" len=%d", length);
  243.         if (length && p < snapend) {
  244.             length = snapend - p;
  245.             default_print(p, length);
  246.         }
  247.         return;
  248.     }
  249.     if (vflag)
  250.         while (p < ep && li) {
  251.             int op, opli;
  252.             const u_char *q;
  253.  
  254.             if (snapend - p < 2)
  255.                 return;
  256.             if (li < 2) {
  257.                 printf(" bad opts/li");
  258.                 return;
  259.             }
  260.             op = *p++;
  261.             opli = *p++;
  262.             li -= 2;
  263.             if (opli > li) {
  264.                 printf(" opt (%d) too long", op);
  265.                 return;
  266.             }
  267.             li -= opli;
  268.             q = p;
  269.             p += opli;
  270.             if (snapend < p)
  271.                 return;
  272.             if (op == 198 && opli == 2) {
  273.                 printf(" tmo=%d", q[0] * 256 + q[1]);
  274.                 continue;
  275.             }
  276.             printf (" %d:<", op);
  277.             while (--opli >= 0)
  278.                 printf("%02x", *q++);
  279.             printf (">");
  280.         }
  281. }
  282.  
  283. static int
  284. osi_cksum(register const u_char *p, register int len,
  285.       const u_char *toff, u_char *cksum, u_char *off)
  286. {
  287.     int x, y, f = (len - ((toff - p) + 1));
  288.     long c0 = 0, c1 = 0;
  289.  
  290.     if ((cksum[0] = off[0]) == 0 && (cksum[1] = off[1]) == 0)
  291.         return 0;
  292.  
  293.     off[0] = off[1] = 0;
  294.     while (--len >= 0) {
  295.         c0 += *p++;
  296.         c1 += c0;
  297.         c0 %= 255;
  298.         c1 %= 255;
  299.     }
  300.     x = (c0 * f - c1);
  301.     if (x < 0)
  302.         x = 255 - (-x % 255);
  303.     else
  304.         x %= 255;
  305.     y = -1 * (x + c0);
  306.     if (y < 0)
  307.         y = 255 - (-y % 255);
  308.     else
  309.         y %= 255;
  310.  
  311.     off[0] = x;
  312.     off[1] = y;
  313.  
  314.     return (off[0] != cksum[0] || off[1] != cksum[1]);
  315. }
  316.